package com.jianjun.ktui.ui

import androidx.compose.animation.*
import androidx.compose.animation.core.*
import androidx.compose.foundation.Image
import androidx.compose.foundation.layout.Column
import androidx.compose.foundation.layout.fillMaxSize
import androidx.compose.foundation.layout.padding
import androidx.compose.foundation.rememberScrollState
import androidx.compose.foundation.verticalScroll
import androidx.compose.material.icons.Icons
import androidx.compose.material.icons.automirrored.filled.ArrowBack
import androidx.compose.material.icons.filled.Close
import androidx.compose.material.icons.filled.Menu
import androidx.compose.material3.*
import androidx.compose.runtime.*
import androidx.compose.ui.Alignment
import androidx.compose.ui.Modifier
import androidx.compose.ui.graphics.Color
import androidx.compose.ui.graphics.graphicsLayer
import androidx.compose.ui.layout.ContentScale
import androidx.compose.ui.unit.dp
import androidx.compose.ui.window.Dialog
import androidx.lifecycle.viewmodel.compose.viewModel
import androidx.navigation.*
import androidx.navigation.compose.NavHost
import androidx.navigation.compose.composable
import androidx.navigation.compose.currentBackStackEntryAsState
import androidx.navigation.compose.rememberNavController
import androidx.savedstate.SavedState
import androidx.savedstate.read
import com.jianjun.ktui.Method
import com.jianjun.ktui.getPlatform
import com.jianjun.ktui.httpRuoYi
import com.jianjun.ktui.ui.data.UserStore
import com.jianjun.ktui.ui.screen.*
import jianjun_gradle.composeapp.generated.resources.*
import kotlinx.coroutines.CoroutineScope
import kotlinx.coroutines.delay
import kotlinx.coroutines.launch
import org.jetbrains.compose.resources.StringResource
import org.jetbrains.compose.resources.painterResource
import org.jetbrains.compose.resources.stringResource
import org.jetbrains.compose.ui.tooling.preview.Preview

/**
 * 表示应用程序中屏幕的枚举值
 */
enum class RuoYiScreen(val title: StringResource) {
    Login(title = Res.string.login),
    Register(title = Res.string.register),
    Index(title = Res.string.index),
    OperLog(title = Res.string.index),
    LoginInfor(title = Res.string.index),
    Job(title = Res.string.index),
    Online(title = Res.string.index),
    Notice(title = Res.string.index),
    Config(title = Res.string.index),
    Dict(title = Res.string.index),
    Post(title = Res.string.index),
    Dept(title = Res.string.index),
    Menu(title = Res.string.index),
    Role(title = Res.string.index),
    User(title = Res.string.index),
}

/**
 * 创建应用程序的主函数
 * @param viewModel BundleViewModel
 * @param navController NavHostController
 */
@OptIn(ExperimentalMaterial3Api::class)
@Composable
@Suppress("UNCHECKED_CAST")
fun RuoYiApp(
    //viewModel: BundleViewModel = viewModel { BundleViewModel() },
    viewModel: SavedStateViewModel = viewModel { SavedStateViewModel() },
    navController: NavHostController = rememberNavController()
) {
    val scope = rememberCoroutineScope()
    //获取当前后堆栈条目
    val backStackEntry by navController.currentBackStackEntryAsState()
    //获取当前屏幕的名称
    val currentScreen = RuoYiScreen.valueOf(
        backStackEntry?.destination?.route ?: RuoYiScreen.Login.name
    )
    val snackbarHostState = remember { SnackbarHostState() }
    val drawerState = rememberDrawerState(initialValue = DrawerValue.Closed)
    //验证码
    var imageUrl by remember { mutableStateOf("") }
    var loadingDialog by remember { mutableStateOf(false) }
    var loadingClose by remember { mutableStateOf(false) }
    var routers by remember { mutableStateOf(mutableListOf<MutableMap<String, Any>>()) }
    var rows by remember { mutableStateOf(mutableListOf<MutableMap<String, Any>>()) }
    navController.addOnDestinationChangedListener { _: NavController, destination: NavDestination, _: SavedState? ->
        run {
            if (backStackEntry?.destination != destination) {
                rows.clear()
            }
        }
    }
    //创建一个 InfiniteTransition 实例来管理子动画：
    val infiniteTransition = rememberInfiniteTransition()
    val rotation by infiniteTransition.animateFloat(
        initialValue = 0f, targetValue = 360f, animationSpec = infiniteRepeatable(
            animation = tween(durationMillis = 2000), repeatMode = RepeatMode.Restart
        )
    )
    scope.launch {
        loadingDialog
        routers
    }
    when {
        loadingDialog -> {
            loadingClose = false
            Dialog(onDismissRequest = {}) {
                Column(horizontalAlignment = Alignment.CenterHorizontally) {
                    Image(
                        painter = painterResource(Res.drawable.loading),
                        contentDescription = null,
                        contentScale = ContentScale.FillBounds,
                        modifier = Modifier.graphicsLayer(rotationZ = rotation),
                    )
                    Text("请稍后...", color = Color(0xffe6e6e6))
                    if (loadingClose) {
                        IconButton(onClick = {
                            loadingDialog = false
                        }) {
                            Icon(Icons.Filled.Close, null)
                        }
                    }
                }
            }
            scope.launch {
                delay(10 * 1000)
                loadingClose = true
            }
        }
    }
    ModalNavigationDrawer(
        drawerContent = {
            ModalDrawerSheet {
                Column(
                    modifier = Modifier.padding(horizontal = 16.dp).verticalScroll(rememberScrollState())
                ) {
                    if (routers.isNotEmpty()) {
                        NavigationDrawerItem(label = { Text(text = "首页") }, selected = false, onClick = {
                            navController.navigate(RuoYiScreen.Index.name)
                        })
                        NavigationDrawerItem(label = { Text(text = "登出") }, selected = false, onClick = {
                            scope.launch {
                                loadingDialog = true
                                try {
                                    val map = mutableMapOf<String, Any>()
                                    val resMap: MutableMap<String, Any> = httpRuoYi("/logout", map, Method.POST)
                                    resMap.clear()
                                } catch (e: Exception) {
                                    toast(scope, snackbarHostState, e.message)
                                } finally {
                                    loadingDialog = false
                                    drawerState.close()
                                    routers.clear()
                                    navController.navigate(RuoYiScreen.Login.name) {
                                        popUpTo(RuoYiScreen.Login.name) {
                                            inclusive = true
                                        }
                                    }
                                }
                            }
                        })
                    }
                    routers.forEach {
                        GetRouters(it, navController, scope, snackbarHostState)
                    }
                }
            }
        }, gesturesEnabled = drawerState.isOpen || routers.isNotEmpty(), drawerState = drawerState
    ) {
        Scaffold(
            topBar = {
                if (getPlatform().isAppBar) {
                    TopAppBar(
                        title = { Text(stringResource(currentScreen.title)) },
                        colors = TopAppBarDefaults.topAppBarColors(
                            containerColor = MaterialTheme.colorScheme.primaryContainer
                        ),
                        navigationIcon = {
                            if (navController.previousBackStackEntry != null) {
                                IconButton(onClick = { navController.navigateUp() }) {
                                    Icon(
                                        imageVector = Icons.AutoMirrored.Filled.ArrowBack,
                                        contentDescription = stringResource(Res.string.back_button)
                                    )
                                }
                            }
                        },
                        actions = {
                            IconButton(onClick = {
                                scope.launch {
                                    if (drawerState.isClosed) {
                                        drawerState.open()
                                    } else {
                                        drawerState.close()
                                    }
                                }
                            }) {
                                Icon(Icons.Filled.Menu, contentDescription = "Menu")
                            }
                        })
                }
            },
            snackbarHost = {
                SnackbarHost(hostState = snackbarHostState)
            },

            ) { innerPadding ->
            val uiState by viewModel.uiState.collectAsState()

            NavHost(
                navController = navController,
                contentAlignment = Alignment.Center,
                //设置导航的背景颜色
                startDestination = RuoYiScreen.Login.name,
                modifier = Modifier.fillMaxSize().verticalScroll(rememberScrollState()).padding(innerPadding)
            ) {
                //滑动过渡动画
                composableSlide(route = RuoYiScreen.Login.name) {
                    LoginScreen(showSnackbar = {
                        toast(scope, snackbarHostState, it)
                    }, uiState = uiState, imageUrl = imageUrl, onLoginClicked = {
                        scope.launch {
                            loadingDialog = true
                            val map = uiState.read {
                                mutableMapOf<String, Any>(
                                    "username" to getString("username"),
                                    "password" to getString("password"),
                                    "code" to getString("code"),
                                    "uuid" to UserStore.captchaKey
                                )
                            }
                            var resMap: MutableMap<String, Any>
                            try {
                                resMap = httpRuoYi("/login", map, Method.POST)
                                UserStore.token = resMap["token"] as? String ?: ""
                                resMap = httpRuoYi("/getInfo", map, Method.GET)
                                UserStore.id = (resMap["user"] as Map<*, *>)["userId"].toString()
                                UserStore.name = (resMap["user"] as Map<*, *>)["userName"] as? String ?: ""
                                UserStore.roles = resMap["roles"] as MutableList<String>
                                if (UserStore.roles.isEmpty()) {
                                    UserStore.roles = mutableListOf("ROLE_DEFAULT")
                                } else {
                                    UserStore.permissions = resMap["permissions"] as MutableList<String>
                                }
                                resMap = httpRuoYi("/getRouters", map, Method.GET)
                                routers = resMap["data"] as MutableList<MutableMap<String, Any>>
                                //UserStore.routers = routers
                                //toast(scope, snackbarHostState, resMap["msg"] as? String ?: "")
                                navController.navigate(RuoYiScreen.Index.name)
                                imageUrl = ""
                            } catch (e: Exception) {
                                toast(scope, snackbarHostState, e.message)
                                resMap = httpRuoYi("/logout", map, Method.POST)
                                resMap.clear()
                                UserStore.token = ""
                                imageUrl = ""
                            } finally {
                                loadingDialog = false
                            }
                        }
                    }, onCodeClicked = {
                        scope.launch {
                            loadingDialog = true
                            try {
                                val map = mutableMapOf<String, Any>()
                                val resMap: MutableMap<String, Any> = httpRuoYi("/captchaImage", map, Method.GET)
                                UserStore.captchaKey = resMap["uuid"] as? String ?: ""
                                imageUrl = "data:image/gif;base64," + (resMap["img"] as? String ?: "")
                            } catch (e: Exception) {
                                toast(scope, snackbarHostState, e.message)
                            } finally {
                                loadingDialog = false
                            }
                        }
                    }, toRegisterClicked = {
                        navController.navigate(RuoYiScreen.Register.name)
                    })
                }
                composableSlide(route = RuoYiScreen.Register.name) {
                    RegisterScreen(showSnackbar = {
                        toast(scope, snackbarHostState, it)
                    }, uiState = uiState, toLoginClicked = {
                        navController.navigate(RuoYiScreen.Login.name)
                    }, imageUrl = imageUrl, onRegisterClicked = {
                        scope.launch {
                            loadingDialog = true
                            try {
                                val map = uiState.read {
                                    mutableMapOf<String, Any>(
                                        "username" to getString("username"),
                                        "password" to getString("password"),
                                        "code" to getString("code"),
                                        "uuid" to UserStore.captchaKey
                                    )
                                }
                                val resMap: MutableMap<String, Any> = httpRuoYi("/register", map, Method.POST)
                                toast(scope, snackbarHostState, resMap["msg"] as? String ?: "")
                            } catch (e: Exception) {
                                toast(scope, snackbarHostState, e.message)
                            } finally {
                                loadingDialog = false
                            }
                        }
                    }, onCodeClicked = {
                        scope.launch {
                            loadingDialog = true
                            try {
                                val map = mutableMapOf<String, Any>()
                                val resMap: MutableMap<String, Any> = httpRuoYi("/captchaImage", map, Method.GET)
                                UserStore.captchaKey = resMap["uuid"] as? String ?: ""
                                imageUrl = "data:image/gif;base64," + (resMap["img"] as? String ?: "")
                            } catch (e: Exception) {
                                toast(scope, snackbarHostState, e.message)
                            } finally {
                                loadingDialog = false
                            }
                        }
                    })
                }
                composableSlide(route = RuoYiScreen.Index.name) {
                    IndexScreen(
                        showSnackbar = {
                            toast(scope, snackbarHostState, it)
                        }, uiState = uiState
                    )
                }
                composableSlide(route = RuoYiScreen.OperLog.name) {
                    OperLogScreen(
                        showSnackbar = {
                            toast(scope, snackbarHostState, it)
                        }, uiState = uiState, onQueryClicked = {
                            scope.launch {
                                loadingDialog = true
                                try {
                                    var map = uiState.read {
                                        mutableMapOf<String, Any>(
                                            "pageNum" to 1, "pageSize" to 100,
                                            "operIp" to getString("operIp"),
                                            "title" to getString("title"),
                                            "operName" to getString("operName"),
                                            "businessType" to getString("businessType"),
                                            "status" to getString("status"),
                                            "params[beginTime]" to getString("beginTime"),
                                            "params[endTime]" to getString("endTime")
                                        )
                                    }
                                    map = map.filter { it.value != "" }.toMutableMap()
                                    val resMap: MutableMap<String, Any> =
                                        httpRuoYi("/monitor/operlog/list", map, Method.GET)
                                    rows = resMap["rows"] as MutableList<MutableMap<String, Any>>
                                    //toast(scope, snackbarHostState, resMap["msg"] as? String ?: "")
                                } catch (e: Exception) {
                                    toast(scope, snackbarHostState, e.message)
                                } finally {
                                    loadingDialog = false
                                }
                            }
                        }, rows = rows
                    )
                }
                composableSlide(route = RuoYiScreen.LoginInfor.name) {
                    LoginInforScreen(
                        showSnackbar = {
                            toast(scope, snackbarHostState, it)
                        }, uiState = uiState, onQueryClicked = {
                            scope.launch {
                                loadingDialog = true
                                try {
                                    var map = uiState.read {
                                        mutableMapOf<String, Any>(
                                            "pageNum" to 1, "pageSize" to 100,
                                            "ipaddr" to getString("ipaddr"),
                                            "userName" to getString("userName"),
                                            "status" to getString("status"),
                                            "params[beginTime]" to getString("beginTime"),
                                            "params[endTime]" to getString("endTime")
                                        )
                                    }
                                    map = map.filter { it.value != "" }.toMutableMap()
                                    val resMap: MutableMap<String, Any> =
                                        httpRuoYi("/monitor/logininfor/list", map, Method.GET)
                                    rows = resMap["rows"] as MutableList<MutableMap<String, Any>>
                                    //toast(scope, snackbarHostState, resMap["msg"] as? String ?: "")
                                } catch (e: Exception) {
                                    toast(scope, snackbarHostState, e.message)
                                } finally {
                                    loadingDialog = false
                                }
                            }
                        }, rows = rows
                    )
                }
                composableSlide(route = RuoYiScreen.Job.name) {
                    JobScreen(
                        showSnackbar = {
                            toast(scope, snackbarHostState, it)
                        }, uiState = uiState, onQueryClicked = {
                            scope.launch {
                                loadingDialog = true
                                try {
                                    var map = uiState.read {
                                        mutableMapOf<String, Any>(
                                            "pageNum" to 1, "pageSize" to 100,
                                            "jobName" to getString("jobName"),
                                            "jobGroup" to getString("jobGroup"),
                                            "status" to getString("status"),
                                        )
                                    }
                                    map = map.filter { it.value != "" }.toMutableMap()
                                    val resMap: MutableMap<String, Any> =
                                        httpRuoYi("/monitor/job/list", map, Method.GET)
                                    rows = resMap["rows"] as MutableList<MutableMap<String, Any>>
                                } catch (e: Exception) {
                                    toast(scope, snackbarHostState, e.message)
                                } finally {
                                    loadingDialog = false
                                }
                            }
                        }, rows = rows
                    )
                }
                composableSlide(route = RuoYiScreen.Online.name) {
                    OnlineScreen(
                        showSnackbar = {
                            toast(scope, snackbarHostState, it)
                        }, uiState = uiState, onQueryClicked = {
                            scope.launch {
                                loadingDialog = true
                                try {
                                    var map = uiState.read {
                                        mutableMapOf<String, Any>(
                                            "pageNum" to 1, "pageSize" to 100,
                                            "ipaddr" to getString("ipaddr"),
                                            "userName" to getString("userName"),
                                        )
                                    }
                                    map = map.filter { it.value != "" }.toMutableMap()
                                    val resMap: MutableMap<String, Any> =
                                        httpRuoYi("/monitor/online/list", map, Method.GET)
                                    rows = resMap["rows"] as MutableList<MutableMap<String, Any>>
                                } catch (e: Exception) {
                                    toast(scope, snackbarHostState, e.message)
                                } finally {
                                    loadingDialog = false
                                }
                            }
                        }, rows = rows
                    )
                }
                composableSlide(route = RuoYiScreen.Notice.name) {
                    NoticeScreen(
                        showSnackbar = {
                            toast(scope, snackbarHostState, it)
                        }, uiState = uiState, onQueryClicked = {
                            scope.launch {
                                loadingDialog = true
                                try {
                                    var map = uiState.read {
                                        mutableMapOf<String, Any>(
                                            "pageNum" to 1, "pageSize" to 100,
                                            "noticeTitle" to getString("noticeTitle"),
                                            "noticeType" to getString("noticeType"),
                                            "createBy" to getString("createBy"),
                                        )
                                    }
                                    map = map.filter { it.value != "" }.toMutableMap()
                                    val resMap: MutableMap<String, Any> =
                                        httpRuoYi("/system/notice/list", map, Method.GET)
                                    rows = resMap["rows"] as MutableList<MutableMap<String, Any>>
                                } catch (e: Exception) {
                                    toast(scope, snackbarHostState, e.message)
                                } finally {
                                    loadingDialog = false
                                }
                            }
                        }, rows = rows
                    )
                }
                composableSlide(route = RuoYiScreen.Config.name) {
                    ConfigScreen(
                        showSnackbar = {
                            toast(scope, snackbarHostState, it)
                        }, uiState = uiState, onQueryClicked = {
                            scope.launch {
                                loadingDialog = true
                                try {
                                    var map = uiState.read {
                                        mutableMapOf<String, Any>(
                                            "pageNum" to 1, "pageSize" to 100,
                                            "configName" to getString("configName"),
                                            "configKey" to getString("configKey"),
                                            "configType" to getString("configType"),
                                            "params[beginTime]" to getString("beginTime"),
                                            "params[endTime]" to getString("endTime")
                                        )
                                    }
                                    map = map.filter { it.value != "" }.toMutableMap()
                                    val resMap: MutableMap<String, Any> =
                                        httpRuoYi("/system/config/list", map, Method.GET)
                                    rows = resMap["rows"] as MutableList<MutableMap<String, Any>>
                                } catch (e: Exception) {
                                    toast(scope, snackbarHostState, e.message)
                                } finally {
                                    loadingDialog = false
                                }
                            }
                        }, rows = rows
                    )
                }
                composableSlide(route = RuoYiScreen.Dict.name) {
                    DictScreen(
                        showSnackbar = {
                            toast(scope, snackbarHostState, it)
                        }, uiState = uiState, onQueryClicked = {
                            scope.launch {
                                loadingDialog = true
                                try {
                                    var map = uiState.read {
                                        mutableMapOf<String, Any>(
                                            "pageNum" to 1, "pageSize" to 100,
                                            "dictName" to getString("dictName"),
                                            "dictType" to getString("dictType"),
                                            "status" to getString("status"),
                                            "params[beginTime]" to getString("beginTime"),
                                            "params[endTime]" to getString("endTime")
                                        )
                                    }
                                    map = map.filter { it.value != "" }.toMutableMap()
                                    val resMap: MutableMap<String, Any> =
                                        httpRuoYi("/system/dict/type/list", map, Method.GET)
                                    rows = resMap["rows"] as MutableList<MutableMap<String, Any>>
                                } catch (e: Exception) {
                                    toast(scope, snackbarHostState, e.message)
                                } finally {
                                    loadingDialog = false
                                }
                            }
                        }, rows = rows
                    )
                }
                composableSlide(route = RuoYiScreen.Post.name) {
                    PostScreen(
                        showSnackbar = {
                            toast(scope, snackbarHostState, it)
                        }, uiState = uiState, onQueryClicked = {
                            scope.launch {
                                loadingDialog = true
                                try {
                                    var map = uiState.read {
                                        mutableMapOf<String, Any>(
                                            "pageNum" to 1, "pageSize" to 100,
                                            "postCode" to getString("postCode"),
                                            "postName" to getString("postName"),
                                            "status" to getString("status"),
                                        )
                                    }
                                    map = map.filter { it.value != "" }.toMutableMap()
                                    val resMap: MutableMap<String, Any> =
                                        httpRuoYi("/system/post/list", map, Method.GET)
                                    rows = resMap["rows"] as MutableList<MutableMap<String, Any>>
                                } catch (e: Exception) {
                                    toast(scope, snackbarHostState, e.message)
                                } finally {
                                    loadingDialog = false
                                }
                            }
                        }, rows = rows
                    )
                }
                composableSlide(route = RuoYiScreen.Dept.name) {
                    DeptScreen(
                        showSnackbar = {
                            toast(scope, snackbarHostState, it)
                        }, uiState = uiState, onQueryClicked = {
                            scope.launch {
                                loadingDialog = true
                                try {
                                    var map = uiState.read {
                                        mutableMapOf<String, Any>(
                                            "pageNum" to 1, "pageSize" to 100,
                                            "deptName" to getString("deptName"),
                                            "status" to getString("status"),
                                        )
                                    }
                                    map = map.filter { it.value != "" }.toMutableMap()
                                    val resMap: MutableMap<String, Any> =
                                        httpRuoYi("/system/dept/list", map, Method.GET)
                                    rows = resMap["data"] as MutableList<MutableMap<String, Any>>
                                } catch (e: Exception) {
                                    toast(scope, snackbarHostState, e.message)
                                } finally {
                                    loadingDialog = false
                                }
                            }
                        }, rows = rows
                    )
                }
                composableSlide(route = RuoYiScreen.Menu.name) {
                    MenuScreen(
                        showSnackbar = {
                            toast(scope, snackbarHostState, it)
                        }, uiState = uiState, onQueryClicked = {
                            scope.launch {
                                loadingDialog = true
                                try {
                                    var map = uiState.read {
                                        mutableMapOf<String, Any>(
                                            "pageNum" to 1, "pageSize" to 100,
                                            "menuName" to getString("menuName"),
                                            "status" to getString("status"),
                                        )
                                    }
                                    map = map.filter { it.value != "" }.toMutableMap()
                                    val resMap: MutableMap<String, Any> =
                                        httpRuoYi("/system/menu/list", map, Method.GET)
                                    rows = resMap["data"] as MutableList<MutableMap<String, Any>>
                                } catch (e: Exception) {
                                    toast(scope, snackbarHostState, e.message)
                                } finally {
                                    loadingDialog = false
                                }
                            }
                        }, rows = rows
                    )
                }
                composableSlide(route = RuoYiScreen.Role.name) {
                    RoleScreen(
                        showSnackbar = {
                            toast(scope, snackbarHostState, it)
                        }, uiState = uiState, onQueryClicked = {
                            scope.launch {
                                loadingDialog = true
                                try {
                                    var map = uiState.read {
                                        mutableMapOf<String, Any>(
                                            "pageNum" to 1, "pageSize" to 100,
                                            "roleName" to getString("roleName"),
                                            "roleKey" to getString("roleKey"),
                                            "status" to getString("status"),
                                            "params[beginTime]" to getString("beginTime"),
                                            "params[endTime]" to getString("endTime")
                                        )
                                    }
                                    map = map.filter { it.value != "" }.toMutableMap()
                                    val resMap: MutableMap<String, Any> =
                                        httpRuoYi("/system/role/list", map, Method.GET)
                                    rows = resMap["rows"] as MutableList<MutableMap<String, Any>>
                                } catch (e: Exception) {
                                    toast(scope, snackbarHostState, e.message)
                                } finally {
                                    loadingDialog = false
                                }
                            }
                        }, rows = rows
                    )
                }
                composableSlide(route = RuoYiScreen.User.name) {
                    UserScreen(
                        showSnackbar = {
                            toast(scope, snackbarHostState, it)
                        }, uiState = uiState, onQueryClicked = {
                            scope.launch {
                                loadingDialog = true
                                try {
                                    var map = uiState.read {
                                        mutableMapOf<String, Any>(
                                            "pageNum" to 1, "pageSize" to 100,
                                            "userName" to getString("userName"),
                                            "phonenumber" to getString("phonenumber"),
                                            "status" to getString("status"),
                                            "params[beginTime]" to getString("beginTime"),
                                            "params[endTime]" to getString("endTime")
                                        )
                                    }
                                    map = map.filter { it.value != "" }.toMutableMap()
                                    val resMap: MutableMap<String, Any> =
                                        httpRuoYi("/system/user/list", map, Method.GET)
                                    rows = resMap["rows"] as MutableList<MutableMap<String, Any>>
                                } catch (e: Exception) {
                                    toast(scope, snackbarHostState, e.message)
                                } finally {
                                    loadingDialog = false
                                }
                            }
                        }, rows = rows
                    )
                }
            }
        }
    }
}


private fun toast(scope: CoroutineScope, snackbarHostState: SnackbarHostState, message: String?) {
    scope.launch {
        val result = snackbarHostState.showSnackbar(message ?: "", withDismissAction = true)
        when (result) {
            //点击了 显示时配置的 Action 按钮
            SnackbarResult.ActionPerformed -> {}
            //点击了 X 按钮
            SnackbarResult.Dismissed -> {}
        }
    }
}

@Composable
@Suppress("UNCHECKED_CAST")
private fun GetRouters(
    it: MutableMap<String, Any>,
    navController: NavHostController,
    scope: CoroutineScope,
    snackbarHostState: SnackbarHostState,
    index: Int = 1
) {
    if (!(it["hidden"] as Boolean)) {
        if ((it["redirect"] as? String ?: "") == "noRedirect") {
            HorizontalDivider()
            Text(
                (it["meta"] as Map<*, *>)["title"] as? String ?: "",
                modifier = Modifier.padding(start = (index * 16).dp, top = 16.dp, bottom = 16.dp, end = 16.dp)
            )
        } else {
            NavigationDrawerItem(
                label = { Text(text = (it["meta"] as Map<*, *>)["title"] as? String ?: "") },
                selected = false,
                onClick = {
                    val component = it["component"] as? String ?: ""
                    when {
                        component.contains(
                            RuoYiScreen.OperLog.name, true
                        ) -> navController.navigate(RuoYiScreen.OperLog.name)

                        component.contains(
                            RuoYiScreen.LoginInfor.name, true
                        ) -> navController.navigate(RuoYiScreen.LoginInfor.name)

                        component.contains(
                            RuoYiScreen.Job.name, true
                        ) -> navController.navigate(RuoYiScreen.Job.name)

                        component.contains(
                            RuoYiScreen.Online.name, true
                        ) -> navController.navigate(RuoYiScreen.Online.name)

                        component.contains(
                            RuoYiScreen.Notice.name, true
                        ) -> navController.navigate(RuoYiScreen.Notice.name)

                        component.contains(
                            RuoYiScreen.Config.name, true
                        ) -> navController.navigate(RuoYiScreen.Config.name)

                        component.contains(
                            RuoYiScreen.Dict.name, true
                        ) -> navController.navigate(RuoYiScreen.Dict.name)

                        component.contains(
                            RuoYiScreen.Post.name, true
                        ) -> navController.navigate(RuoYiScreen.Post.name)

                        component.contains(
                            RuoYiScreen.Dept.name, true
                        ) -> navController.navigate(RuoYiScreen.Dept.name)

                        component.contains(
                            RuoYiScreen.Menu.name, true
                        ) -> navController.navigate(RuoYiScreen.Menu.name)

                        component.contains(
                            RuoYiScreen.Role.name, true
                        ) -> navController.navigate(RuoYiScreen.Role.name)

                        component.contains(
                            RuoYiScreen.User.name, true
                        ) -> navController.navigate(RuoYiScreen.User.name)

                        else -> toast(scope, snackbarHostState, (it["meta"] as Map<*, *>)["title"] as? String ?: "")
                    }
                },
                modifier = Modifier.padding(start = (index * 16).dp)
            )
        }

        (it["children"] as? List<MutableMap<String, Any>> ?: listOf()).forEach { itc ->
            GetRouters(itc, navController, scope, snackbarHostState, index + 1)
        }
    }
}

fun NavGraphBuilder.composableSlide(
    route: String,
    arguments: List<NamedNavArgument> = emptyList(),
    deepLinks: List<NavDeepLink> = emptyList(),
    content: @Composable (NavBackStackEntry) -> Unit
) {
    composable(route = route, arguments = arguments, deepLinks = deepLinks, enterTransition = {
        // 新页面：从右到左滑入 + 渐变显示
        slideInHorizontally(initialOffsetX = { it }, animationSpec = tween(300)) + fadeIn(
            animationSpec = tween(300)
        )
    }, exitTransition = {
        // 旧页面：缩小消失 + 渐变消失
        scaleOut(targetScale = 0.8f, animationSpec = tween(300)) + fadeOut(animationSpec = tween(300))
    }, popEnterTransition = {
        // 返回时：新页面从小到大缩放 + 渐变显示
        scaleIn(initialScale = 0.8f, animationSpec = tween(300)) + fadeIn(animationSpec = tween(300))
    }, popExitTransition = {
        // 返回时：旧页面从左到右滑出 + 渐变消失
        slideOutHorizontally(targetOffsetX = { it }, animationSpec = tween(300)) + fadeOut(
            animationSpec = tween(300)
        )
    }) { entry ->
        content(entry)
    }
}


@Preview(widthDp = 700, heightDp = 500)
@Composable
fun RuoYiAppPreview() {
    RuoYiApp()
}